const ffmpeg = require('fluent-ffmpeg');
const ffmpegPath = require('@ffmpeg-installer/ffmpeg').path;
const ffprobePath = require('@ffprobe-installer/ffprobe').path;
const path = require('path');
const fs = require('fs');
const logger = require('./logger');

// 设置 ffmpeg 和 ffprobe 路径
ffmpeg.setFfmpegPath(ffmpegPath);
ffmpeg.setFfprobePath(ffprobePath);

/**
 * 获取视频信息
 * @param {string} videoPath - 视频文件路径
 * @returns {Promise<Object>} 视频信息
 */
function getVideoInfo(videoPath) {
  return new Promise((resolve, reject) => {
    ffmpeg.ffprobe(videoPath, (err, metadata) => {
      if (err) {
        logger.error('获取视频信息失败:', err);
        reject(err);
      } else {
        resolve(metadata);
      }
    });
  });
}

/**
 * 视频转码 - 转换为兼容性更好的格式
 * @param {string} inputPath - 输入视频路径
 * @param {string} outputPath - 输出视频路径
 * @param {Object} options - 转码选项
 * @returns {Promise<Object>} 转码结果
 */
function transcodeVideo(inputPath, outputPath, options = {}) {
  return new Promise(async (resolve, reject) => {
    try {
      // 先获取视频信息
      const metadata = await getVideoInfo(inputPath);
      const videoStream = metadata.streams.find(s => s.codec_type === 'video');
      
      logger.info('开始转码视频:', {
        input: inputPath,
        output: outputPath,
        originalCodec: videoStream?.codec_name,
        originalProfile: videoStream?.profile,
        originalSize: `${videoStream?.width}x${videoStream?.height}`
      });

      // 默认转码配置 - 使用 Baseline Profile 以获得最佳兼容性
      const defaultOptions = {
        videoCodec: 'libx264',
        videoProfile: 'baseline',  // 最重要：使用 baseline profile
        videoLevel: '3.0',         // Level 3.0 更兼容老设备
        videoBitrate: '1500k',     // 码率
        maxrate: '1500k',          // 最大码率
        bufsize: '3000k',          // 缓冲区大小
        preset: 'medium',          // 编码速度预设
        crf: 23,                   // 质量控制 (18-28, 值越小质量越高)
        pixelFormat: 'yuv420p',    // 色彩格式
        audioCodec: 'aac',
        audioBitrate: '128k',
        audioChannels: 2,
        size: '1280x720',          // 限制最大分辨率，提高兼容性
        faststart: true,           // 优化流式播放
        ...options
      };

      const command = ffmpeg(inputPath)
        .videoCodec(defaultOptions.videoCodec)
        .addOutputOptions([
          `-profile:v ${defaultOptions.videoProfile}`,
          `-level ${defaultOptions.videoLevel}`,
          `-preset ${defaultOptions.preset}`,
          `-crf ${defaultOptions.crf}`,
          `-maxrate ${defaultOptions.maxrate}`,
          `-bufsize ${defaultOptions.bufsize}`,
          `-pix_fmt ${defaultOptions.pixelFormat}`,
          // 明确设置色彩空间（解决 Android MediaCodec 兼容性问题）
          '-colorspace bt709',
          '-color_primaries bt709',
          '-color_trc bt709',
          '-color_range tv',
          // 添加兼容性标记
          '-flags +global_header',
          '-flags:v +global_header'
        ])
        .videoBitrate(defaultOptions.videoBitrate)
        .audioCodec(defaultOptions.audioCodec)
        .audioBitrate(defaultOptions.audioBitrate)
        .audioChannels(defaultOptions.audioChannels)
        .size(defaultOptions.size);  // 设置分辨率

      // 优化流式播放
      if (defaultOptions.faststart) {
        command.addOutputOptions(['-movflags', '+faststart']);
      }

      // 开始转码
      const startTime = Date.now();
      let progress = 0;

      command
        .on('start', (commandLine) => {
          logger.info('FFmpeg 命令:', commandLine);
        })
        .on('progress', (progressInfo) => {
          progress = progressInfo.percent || 0;
          if (progress > 0 && progress % 10 < 1) {
            logger.info(`转码进度: ${progress.toFixed(1)}%`);
          }
        })
        .on('end', async () => {
          const duration = ((Date.now() - startTime) / 1000).toFixed(2);
          
          // 获取转码后的视频信息
          const outputMetadata = await getVideoInfo(outputPath);
          const outputVideoStream = outputMetadata.streams.find(s => s.codec_type === 'video');
          
          const stats = fs.statSync(outputPath);
          const inputStats = fs.statSync(inputPath);
          
          const result = {
            success: true,
            duration: `${duration}秒`,
            inputSize: `${(inputStats.size / 1024 / 1024).toFixed(2)} MB`,
            outputSize: `${(stats.size / 1024 / 1024).toFixed(2)} MB`,
            compression: `${((1 - stats.size / inputStats.size) * 100).toFixed(1)}%`,
            codec: outputVideoStream?.codec_name,
            profile: outputVideoStream?.profile,
            size: `${outputVideoStream?.width}x${outputVideoStream?.height}`,
            outputPath
          };
          
          logger.info('视频转码完成:', result);
          resolve(result);
        })
        .on('error', (err) => {
          logger.error('视频转码失败:', err);
          reject(err);
        })
        .save(outputPath);

    } catch (error) {
      logger.error('视频转码异常:', error);
      reject(error);
    }
  });
}

/**
 * 检查视频是否需要转码
 * @param {string} videoPath - 视频文件路径
 * @returns {Promise<Object>} { needsTranscode: boolean, reason: string, metadata: Object }
 */
async function checkNeedsTranscode(videoPath) {
  try {
    const metadata = await getVideoInfo(videoPath);
    const videoStream = metadata.streams.find(s => s.codec_type === 'video');
    
    if (!videoStream) {
      return { needsTranscode: false, reason: '无视频流' };
    }

    const codec = videoStream.codec_name;
    const profile = videoStream.profile?.toLowerCase() || '';
    
    // 检查是否已经是 H.264 Baseline Profile
    if (codec === 'h264' && profile.includes('baseline')) {
      return { 
        needsTranscode: false, 
        reason: '已是最佳兼容格式 (H.264 Baseline)',
        metadata: videoStream
      };
    }

    // 需要转码的情况
    const reasons = [];
    if (codec !== 'h264') {
      reasons.push(`编码格式: ${codec} (推荐: h264)`);
    }
    if (codec === 'h264' && !profile.includes('baseline')) {
      reasons.push(`Profile: ${profile} (推荐: baseline)`);
    }

    return {
      needsTranscode: reasons.length > 0,
      reason: reasons.join(', '),
      metadata: videoStream
    };
  } catch (error) {
    logger.error('检查视频失败:', error);
    throw error;
  }
}

/**
 * 自动转码视频（如果需要）
 * @param {string} inputPath - 输入视频路径
 * @param {Object} options - 转码选项
 * @returns {Promise<Object>} { transcoded: boolean, outputPath: string, ... }
 */
async function autoTranscodeIfNeeded(inputPath, options = {}) {
  try {
    const check = await checkNeedsTranscode(inputPath);
    
    if (!check.needsTranscode) {
      logger.info('视频无需转码:', check.reason);
      return {
        transcoded: false,
        reason: check.reason,
        outputPath: inputPath
      };
    }

    // 生成输出文件名
    const dir = path.dirname(inputPath);
    const ext = path.extname(inputPath);
    const basename = path.basename(inputPath, ext);
    const outputPath = options.outputPath || path.join(dir, `${basename}_transcoded.mp4`);

    logger.info('视频需要转码:', check.reason);
    
    // 执行转码
    const result = await transcodeVideo(inputPath, outputPath, options);
    
    // 如果转码成功且配置了替换原文件
    if (options.replaceOriginal) {
      logger.info('替换原文件:', inputPath);
      fs.unlinkSync(inputPath);
      fs.renameSync(outputPath, inputPath);
      result.outputPath = inputPath;
    }
    
    return {
      transcoded: true,
      ...result
    };
  } catch (error) {
    logger.error('自动转码失败:', error);
    throw error;
  }
}

/**
 * 生成视频缩略图
 * @param {string} videoPath - 视频文件路径
 * @param {string} outputPath - 输出图片路径
 * @param {Object} options - 选项
 * @returns {Promise<string>} 缩略图路径
 */
function generateThumbnail(videoPath, outputPath, options = {}) {
  return new Promise((resolve, reject) => {
    const defaultOptions = {
      timestamps: ['50%'],  // 在视频50%位置截图
      size: '640x360',      // 缩略图尺寸
      ...options
    };

    ffmpeg(videoPath)
      .screenshots({
        timestamps: defaultOptions.timestamps,
        filename: path.basename(outputPath),
        folder: path.dirname(outputPath),
        size: defaultOptions.size
      })
      .on('end', () => {
        logger.info('缩略图生成成功:', outputPath);
        resolve(outputPath);
      })
      .on('error', (err) => {
        logger.error('缩略图生成失败:', err);
        reject(err);
      });
  });
}

module.exports = {
  getVideoInfo,
  transcodeVideo,
  checkNeedsTranscode,
  autoTranscodeIfNeeded,
  generateThumbnail
};

